package com.wsh.crawler.service.impl.parser;

import com.wsh.crawler.constant.LanguageEnum;
import com.wsh.crawler.constant.NewsSourceEnum;
import com.wsh.crawler.entity.News;
import io.github.bonigarcia.wdm.WebDriverManager;
import jakarta.annotation.PostConstruct;
import org.jsoup.Jsoup;
import org.jsoup.nodes.Document;
import org.jsoup.nodes.Element;
import org.jsoup.select.Elements;
import org.openqa.selenium.WebDriver;
import org.openqa.selenium.chrome.ChromeDriver;
import org.openqa.selenium.chrome.ChromeOptions;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.time.Duration;
import java.util.ArrayList;
import java.util.Date;
import java.util.List;
import java.util.stream.Collectors;

public class SerieAParser extends AbstractNewsParser {

    private final static Logger LOGGER = LoggerFactory.getLogger(SerieAParser.class);

    public SerieAParser() {
        super(NewsSourceEnum.SERIE_A.getName());
    }

    @PostConstruct
    public void init() {
        // 初始化WebDriverManager，自动下载和管理ChromeDriver
        WebDriverManager.chromedriver().setup();
        LOGGER.info("【意甲解析】Selenium WebDriver 初始化完成");
    }

    @Override
    public List<String> parseArticleLinks(Document doc) {
        LOGGER.info("【意甲解析】开始解析新闻链接 - legaseriea.it/it/latest");

        List<String> links = new ArrayList<>();

        // 意甲官网新闻链接的选择器
        String[] selectors = {
                "a[href*='/it/media/']",             // 意大利语媒体链接
                "a[href*='/en/media/']",             // 英语媒体链接
                "a[href*='/media/']",                // 通用媒体链接
                "a[href*='/it/news/']",              // 意大利语新闻链接
                "a[href*='/en/news/']",              // 英语新闻链接
                "a[href*='/news/']",                 // 通用新闻链接
                ".news-item a",                      // 新闻项目链接
                ".article-item a",                   // 文章项目链接
                ".news-card a",                      // 新闻卡片链接
                "article a",                         // 文章链接
                ".card a",                           // 卡片链接
                "a.news-link",                       // 新闻链接类
                "a.article-link"                     // 文章链接类
        };

        for (String selector : selectors) {
            Elements newsLinks = doc.select(selector);
            LOGGER.info("【意甲解析】选择器 '{}' 找到 {} 个链接", selector, newsLinks.size());

            for (Element link : newsLinks) {
                String href = link.attr("href");
                if (!href.isEmpty()) {
                    String fullUrl = buildFullUrl(href);
                    if (isNewsUrl(fullUrl)) {
                        links.add(fullUrl);
                    }
                }
            }
        }

        List<String> uniqueLinks = links.stream().distinct().collect(Collectors.toList());
        LOGGER.info("【意甲解析】共解析到 {} 个唯一新闻链接", uniqueLinks.size());

        return uniqueLinks;
    }

    @Override
    public News parseArticle(Document doc, String url) {
        LOGGER.info("【意甲解析】正在解析{}的文章", url);

        News article = new News();
        article.setSource(NewsSourceEnum.SERIE_A.getName());
        article.setOriginalUrl(url);
        article.setCrawlTime(new Date());
        article.setLanguage(LanguageEnum.IT.getValue());

        // 解析标题
        parseTitle(doc, article);

        // 解析内容
        parseContent(doc, article);

        // 解析图片和视频
        article.setImageUrls(extractImageUrls(doc));
        article.setVideoUrls(extractVideoUrls(doc));
        article.setCoverUrl(extractCoverImage(doc, article.getImageUrls()));

        LOGGER.info("【意甲解析】文章解析完成：{}", article.getTitle());
        return article;
    }

    /**
     * 解析文章标题
     */
    private void parseTitle(Document doc, News article) {
        LOGGER.info("【意甲解析】开始提取标题");

        String[] titleSelectors = {
                "h1",                               // 页面主标题
                ".page-title",                      // 页面标题类
                ".article-title",                   // 文章标题类
                ".news-title",                      // 新闻标题类
                "title"                             // HTML title标签
        };

        for (String selector : titleSelectors) {
            Element titleElement = doc.selectFirst(selector);
            if (titleElement != null && !titleElement.text().trim().isEmpty()) {
                String title = titleElement.text().trim();

                // 关键修正：去掉末尾的"| News"
                if (title.endsWith("| News")) {
                    title = title.substring(0, title.length() - 6).trim();
                }

                // 过滤掉无效标题
                if (title.length() > 5) {
                    article.setTitle(title);
                    LOGGER.info("【意甲解析】提取标题成功：{}", title);
                    return;
                }
            }
        }

        // 备用方法：从meta标签获取
        Element metaTitle = doc.selectFirst("meta[property=og:title]");
        if (metaTitle != null && !metaTitle.attr("content").isEmpty()) {
            String title = metaTitle.attr("content");
            if (title.endsWith("| News")) {
                title = title.substring(0, title.length() - 6).trim();
            }
            article.setTitle(title);
            LOGGER.info("【意甲解析】从meta标签提取标题：{}", title);
            return;
        }

        LOGGER.warn("【意甲解析】未能提取到文章标题");
    }

    /**
     * 解析文章内容 - 使用Selenium获取动态内容（修复版）
     */
    private void parseContent(Document doc, News article) {
        LOGGER.info("【意甲解析】使用Selenium获取动态内容");

        WebDriver driver = null;
        try {
            // 配置Chrome选项
            ChromeOptions options = new ChromeOptions();
            options.addArguments("--headless");
            options.addArguments("--no-sandbox");
            options.addArguments("--disable-dev-shm-usage");
            options.addArguments("--disable-gpu");
            options.addArguments("--user-agent=Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/91.0.4472.124 Safari/537.36");

            // 启动Chrome
            driver = new ChromeDriver(options);
            driver.manage().timeouts().pageLoadTimeout(Duration.ofSeconds(30));

            // 访问页面
            String url = article.getOriginalUrl();
            LOGGER.info("【意甲解析】正在访问页面：{}", url);
            driver.get(url);

            // 等待内容加载
            Thread.sleep(5000); // 等待5秒让JavaScript执行

            // 获取渲染后的页面源码
            String pageSource = driver.getPageSource();
            LOGGER.info("【意甲解析】获取渲染后页面源码长度：{}", pageSource.length());

            // 使用Jsoup解析渲染后的HTML
            Document freshDoc = Jsoup.parse(pageSource);

            // 现在尝试解析内容 - 修复版本
            Element contentElement = freshDoc.selectFirst("h3.hm-content-text");

            if (contentElement != null) {
                LOGGER.info("【意甲解析】找到h3.hm-content-text元素");

                // 方法1：直接获取整个h3的文本内容（推荐）
                String wholeContent = contentElement.text().trim();
                if (wholeContent.length() > 100) {
                    String finalContent = wholeContent
                            .replaceAll("\\(Foto LaPresse\\)", "")
                            .replaceAll("\\(Foto.*?\\)", "")
                            .replaceAll("www\\.[\\w\\.]+", "")
                            .trim();

                    article.setContent(finalContent);
                    LOGGER.info("【意甲解析】直接获取整个内容成功，长度：{}", finalContent.length());
                    return;
                }

                // 方法2：分别处理不同类型的元素
                LOGGER.info("【意甲解析】尝试分别处理不同元素类型");
                StringBuilder content = new StringBuilder();

                // 获取所有直接子元素
                Elements children = contentElement.children();
                LOGGER.info("【意甲解析】找到{}个子元素", children.size());

                for (Element child : children) {
                    String tagName = child.tagName().toLowerCase();
                    String childText = child.text().trim();

                    if (childText.length() > 5) {
                        switch (tagName) {
                            case "p" -> {
                                LOGGER.debug("【意甲解析】处理p标签：{}", childText.length() > 50 ? childText.substring(0, 50) + "..." : childText);
                                content.append(childText).append("\n\n");
                            }
                            case "ul" -> {
                                LOGGER.debug("【意甲解析】处理ul标签，包含{}个li", child.select("li").size());
                                // 处理ul下的每个li
                                Elements liElements = child.select("li");
                                for (Element li : liElements) {
                                    String liText = li.text().trim();
                                    if (liText.length() > 5) {
                                        content.append("• ").append(liText).append("\n");
                                    }
                                }
                                content.append("\n");
                            }
                            case "ol" -> {
                                LOGGER.debug("【意甲解析】处理ol标签");
                                Elements olLiElements = child.select("li");
                                int counter = 1;
                                for (Element li : olLiElements) {
                                    String liText = li.text().trim();
                                    if (liText.length() > 5) {
                                        content.append(counter++).append(". ").append(liText).append("\n");
                                    }
                                }
                                content.append("\n");
                            }
                            case "div", "span" -> {
                                LOGGER.debug("【意甲解析】处理{}标签：{}", tagName, childText.length() > 50 ? childText.substring(0, 50) + "..." : childText);
                                content.append(childText).append("\n\n");
                            }
                            default -> {
                                LOGGER.debug("【意甲解析】处理其他标签{}：{}", tagName, childText.length() > 50 ? childText.substring(0, 50) + "..." : childText);
                                content.append(childText).append("\n\n");
                            }
                        }
                    }
                }

                if (content.length() > 100) {
                    String finalContent = content.toString()
                            .replaceAll("\\(Foto LaPresse\\)", "")
                            .replaceAll("\\(Foto.*?\\)", "")
                            .replaceAll("www\\.[\\w.]+", "")
                            .replaceAll("\n{3,}", "\n\n") // 合并多个换行符
                            .trim();

                    article.setContent(finalContent);
                    LOGGER.info("【意甲解析】 分别处理元素成功，内容长度：{}", finalContent.length());
                    return;
                }
            }

            // 如果h3没有内容，尝试搜索页面文本
            String pageText = freshDoc.text();
            String[] keywords = {"ACF Fiorentina comunica", "Jacopo Fazzini", "Empoli F.C", "settore giovanile", "GLI EVENTI DI OGGI", "TANTI AUGURI"};

            for (String keyword : keywords) {
                int index = pageText.indexOf(keyword);
                if (index != -1) {
                    LOGGER.info("【意甲解析】找到关键词：{}", keyword);

                    int end = Math.min(index + 1500, pageText.length());
                    String extractedContent = pageText.substring(index, end)
                            .replaceAll("Serie A Enilive.*", "")
                            .replaceAll("\\(Foto.*?\\)", "")
                            .replaceAll("www\\.[\\w.]+", "")
                            .trim();

                    if (extractedContent.length() > 100) {
                        article.setContent(extractedContent);
                        LOGGER.info("【意甲解析】 关键词搜索成功，内容长度：{}", extractedContent.length());
                        return;
                    }
                }
            }

        } catch (Exception e) {
            LOGGER.error("【意甲解析】Selenium解析失败", e);
        } finally {
            // 清理资源
            if (driver != null) {
                try {
                    driver.quit();
                } catch (Exception e) {
                    LOGGER.warn("【意甲解析】关闭WebDriver失败", e);
                }
            }
        }
    }

    @Override
    public String extractCoverImage(Document doc, List<String> otherImageUrls) {
        // 从meta标签获取
        Element metaImage = doc.selectFirst("meta[property=og:image]");
        if (metaImage != null && !metaImage.attr("content").isEmpty()) {
            return metaImage.attr("content");
        }

        // 从Twitter卡片获取
        Element twitterImage = doc.selectFirst("meta[name=twitter:image]");
        if (twitterImage != null && !twitterImage.attr("content").isEmpty()) {
            return twitterImage.attr("content");
        }

        // 从第一张图片获取
        if (!otherImageUrls.isEmpty()) {
            return otherImageUrls.get(0);
        }

        // 从页面主要图片获取
        Element mainImage = doc.selectFirst(".logo-post, .hm-container-post img");
        if (mainImage != null) {
            return mainImage.attr("abs:src");
        }

        return null;
    }

    @Override
    protected List<String> extractImageUrls(Document doc) {
        List<String> imageUrls = new ArrayList<>();

        // 从内容区域提取图片
        String[] imageSelectors = {
                ".hm-container-post img[src]",      // 内容区域图片
                ".hm-content-post img[src]",        // 内容帖子图片
                "img.logo-post[src]",               // logo图片
                "img[src]"                          // 所有图片
        };

        for (String selector : imageSelectors) {
            Elements images = doc.select(selector);
            for (Element img : images) {
                String src = img.attr("abs:src");
                if (isValidImageUrl(src)) {
                    imageUrls.add(src);
                }
            }
        }

        return imageUrls.stream().distinct().collect(Collectors.toList());
    }

    @Override
    protected List<String> extractVideoUrls(Document doc) {
        List<String> videoUrls = new ArrayList<>();

        // YouTube视频
        Elements youtubeFrames = doc.select("iframe[src*=youtube]");
        for (Element frame : youtubeFrames) {
            videoUrls.add(frame.attr("abs:src"));
        }

        // HTML5视频
        Elements videoElements = doc.select("video source[src]");
        for (Element source : videoElements) {
            videoUrls.add(source.attr("abs:src"));
        }

        return videoUrls.stream().distinct().collect(Collectors.toList());
    }

    /**
     * 构建完整URL
     */
    private String buildFullUrl(String href) {
        if (href.startsWith("http")) {
            return href;
        } else if (href.startsWith("/")) {
            return "https://www.legaseriea.it" + href;
        } else {
            return "https://www.legaseriea.it/" + href;
        }
    }

    /**
     * 判断是否为新闻URL
     */
    private boolean isNewsUrl(String url) {
        return url.contains("/media/") ||
                url.contains("/news/") ||
                (url.contains("legaseriea.it") && !url.contains("javascript:") && !url.contains("#"));
    }

    /**
     * 验证图片URL是否有效
     */
    private boolean isValidImageUrl(String src) {
        if (src == null || src.isEmpty()) {
            return false;
        }

        String lowerSrc = src.toLowerCase();
        return (lowerSrc.contains(".jpg") ||
                lowerSrc.contains(".jpeg") ||
                lowerSrc.contains(".png") ||
                lowerSrc.contains(".gif") ||
                lowerSrc.contains(".webp")) &&
                !lowerSrc.contains("logo") &&
                !lowerSrc.contains("icon") &&
                src.length() > 20;
    }
}